﻿using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace _8_2_Gather
{

    
    public class XY : IComparable
    {
        public int x;
        public int y;

        public XY(int x, int y)
        {
            this.x = x;
            this.y = y;
        }

        
        public static XY operator ++ (XY a)
        {
            return new XY(a.x+1, a.y+1);
        }
        
        public static XY operator - (XY a)
        {
            return new XY(-a.x, -a.y);
        }

        public static XY operator -(XY a, XY b)
        {
            return new XY(a.x-b.x, a.y-b.y);
        }

        public static XY operator * (XY a, XY b)
        {
            return new XY(a.x*b.x, a.y*b.y);
        }

        public static XY operator + (XY a, XY b)
        {
            return new XY(a.x + b.x, a.y + b.y);
        }
        public static bool operator <(XY a, XY b)
        {
            if (a.x < b.x)
                return true;
            else if (a.x == b.x)
            {
                if (a.y < b.y)
                    return true;
                return false;
            }
            else
                return false;
        }
        
        public static bool operator > (XY a, XY b)
        {
            if (a.x > b.x)
                return true;
            else if (a.x == b.x)
            {
                if (a.y > b.y)
                    return true;
                return false;
            }
            else
                return false;
        }

        public static bool operator !=(XY a, XY b)
        {
            return !(a.x == b.x && a.y == b.y);
        }

        public static bool operator ==(XY a, XY b)
        {
            return a.x == b.x && a.y == b.y;
        }


        //xy1.Equals(xy2)
        public override bool Equals(object obj)
        {
            //this == xy1  xy2 == obj
            if (obj is XY) //obj.GetType() == typeof(XY)
                return this == (XY)obj;
            else
            {
                //Console.WriteLine("------------------------------");
                throw new ArgumentException("obj is no XY object");
                //return false;
            }
        }
        

        public override string ToString()
        {
            return "XY x:" + x + " y:"+ y;
        }


        //xy1.CompareTo(xy2)
        public int CompareTo(object obj)
        {
            if (this == (XY)obj)
                return 0;
            else if (this > (XY)obj)
                return 1;
            else
                return -1;
        }

        public static implicit operator XYZ(XY xy)
        {
            return new XYZ(xy.x, xy.y, 0);
        }
        
    }

    public class XYZ 
    {
        public int z;
        public int x;
        public int y;
        public XYZ(int x, int y, int z) 
        {
            this.x = x;
            this.y = y;
            this.z = z; 
        }

        public static explicit operator XY(XYZ xyz)
        {
            return new XY(xyz.x, xyz.y);
        }

        public override string ToString()
        {
            return "XYZ x:" + x + " y:" + y + " z:" + z;
        }
    }

    public class XYComparer : IComparer<XY>
    {
        public int Compare(XY x, XY y)
        {
            if (((XY)x).x > ((XY)y).x)
                return 1;
            else if (((XY)x).x == ((XY)y).x)
                return 0;
            else
                return -1;
        }
    }
    class Program
    {

        static void Main(string[] args)
        {

            

            XY xyone = new XY(4,5);
            XYZ xyz = new XYZ(1,2,3);

            //xyone = xyz as XY;

            xyone = (XY)xyz;
            Console.WriteLine(xyone);
            xyz = (XYZ)xyone;
            Console.WriteLine(xyz);
            
            


           

            Console.ReadKey();

            int a = 2, b = 3;
            if (a > b)
                ;

            XY xy1 = new XY(2, 1);
            XY xy2 = new XY(3, 2);
            XY xy3 = new XY(3, 2);
            XY xy4 = new XY(3, 0);
            XY xy5 = new XY(3, 1);
            XY temp = xy1;

            List<XY> list = new List<XY>();
            list.Add(xy1);
            list.Add(xy2);
            list.Add(xy3);
            list.Add(xy4);
            list.Add(xy5);
            list.Add(temp);

            Console.WriteLine( Comparer.Default.Compare(xy3, xy2));
            IComparer<XY> com = new XYComparer();
            list.Sort(com);

            foreach (XY xy in list)
            {
                Console.WriteLine(xy);
            }

            list.Sort();

            foreach (XY xy in list)
            {
                Console.WriteLine(xy);
            }

            Console.ReadKey();

            //Console.WriteLine(xy1.CompareTo(xy2));

            //xy1.Equals(1);
            
            //Console.WriteLine(xy1.Equals(1));

            Console.WriteLine(xy1.Equals(xy2));
            Console.WriteLine(xy2.Equals(xy3));
            Console.WriteLine(xy2.Equals(xy2));
            Console.WriteLine(xy2.Equals(temp));
            
            Console.WriteLine(xy2 == xy3);

            if (xy1 < xy2)
                Console.WriteLine("1");
            else
                Console.WriteLine("2");

            Console.WriteLine(xy1);  //2 1
            Console.WriteLine(xy1++);//2 1
            Console.WriteLine(xy1); //3 2
            Console.WriteLine(++xy1); //4 3
            Console.WriteLine(xy1); //4 3
            

            Console.WriteLine(xy1+xy2);
            Console.WriteLine(xy1 - xy2);
            Console.WriteLine(- xy2);

            //XY xy = xy1 > xy2 ? xy1 : xy2;

            Console.ReadKey();
        }
    }
}
